/**
 * @file flatbuffer_struct_demo.cpp
 * @brief FlatBuffer结构体生成器演示程序
 * 
 * 演示如何使用自动生成的C++结构体与FlatBuffer进行序列化和反序列化
 */

#include <iostream>
#include <vector>
#include <memory>
#include <iomanip>
#include <chrono>

// FlatBuffer相关头文件
#include <flatbuffers/flatbuffers.h>

// 包含生成的FlatBuffer头文件
#include "user_generated.h"
#include "game_example_generated.h"
#include "table_vs_struct_demo_generated.h"

// 包含生成的结构体头文件  
#include "user_structs.h"
#include "game_example_structs.h"
#include "table_vs_struct_demo_structs.h"

// 序列化器相关
#include "serializer/flatbuffer_serializer.h"
using namespace flatbuffers;
namespace demo {

/**
 * @brief 打印二进制数据的十六进制表示
 */
void print_hex_data(const std::vector<uint8_t>& data, const std::string& title) {
    std::cout << "\n=== " << title << " ===\n";
    std::cout << "Size: " << data.size() << " bytes\n";
    std::cout << "Data: ";
    
    for (size_t i = 0; i < std::min(data.size(), size_t(32)); ++i) {
        std::cout << std::hex << std::setw(2) << std::setfill('0') 
                  << static_cast<int>(data[i]) << " ";
        if ((i + 1) % 16 == 0) std::cout << "\n      ";
    }
    
    if (data.size() > 32) {
        std::cout << "... (truncated)";
    }
    std::cout << std::dec << "\n";
}

/**
 * @brief 测试User结构体的序列化和反序列化
 */
void test_user_struct() {
    std::cout << "\n========== User结构体测试 ==========\n";
    
    try {
        // 创建原始数据
        comm::UserMsg original_data;
        original_data.id = 12345;
        original_data.name = "张三";
        original_data.email = "zhangsan@example.com";
        original_data.score = 9527;
        original_data.active = true;
        
        std::cout << "原始数据:\n";
        std::cout << "  ID: " << original_data.id << "\n";
        std::cout << "  姓名: " << original_data.name << "\n";
        std::cout << "  邮箱: " << original_data.email << "\n";
        std::cout << "  分数: " << original_data.score << "\n";
        std::cout << "  活跃: " << (original_data.active ? "是" : "否") << "\n";
        
        // 序列化
        flatbuffers::FlatBufferBuilder builder(1024);
        auto fb_offset = flatbuffers::serialize<::comm::User>(builder, original_data);
        builder.Finish(fb_offset);
        
        // 获取序列化数据
        const uint8_t* buffer_data = builder.GetBufferPointer();
        size_t buffer_size = builder.GetSize();
        std::vector<uint8_t> serialized_data(buffer_data, buffer_data + buffer_size);
        
        print_hex_data(serialized_data, "User序列化数据");
        
        // 反序列化方法1: 直接从FlatBuffer对象
        const ::comm::User* fb_user = flatbuffers::GetRoot<comm::User>(buffer_data);
        comm::UserMsg deserialized_data1;
        if (flatbuffers::deserialize(deserialized_data1, fb_user)) {
            std::cout << "\n反序列化数据1 (从FlatBuffer对象):\n";
            std::cout << "  ID: " << deserialized_data1.id << "\n";
            std::cout << "  姓名: " << deserialized_data1.name << "\n";
            std::cout << "  邮箱: " << deserialized_data1.email << "\n";
            std::cout << "  分数: " << deserialized_data1.score << "\n";
            std::cout << "  活跃: " << (deserialized_data1.active ? "是" : "否") << "\n";
        }
        
        // 反序列化方法2: 静态方法
        comm::UserMsg deserialized_data2 = flatbuffers::from_flatbuffer<comm::UserMsg>(fb_user);
        std::cout << "\n反序列化数据2 (静态方法):\n";
        std::cout << "  ID: " << deserialized_data2.id << "\n";
        std::cout << "  姓名: " << deserialized_data2.name << "\n";
        std::cout << "  邮箱: " << deserialized_data2.email << "\n";
        std::cout << "  分数: " << deserialized_data2.score << "\n";
        std::cout << "  活跃: " << (deserialized_data2.active ? "是" : "否") << "\n";
        
        // 验证数据一致性
        bool data_match = (
            original_data.id == deserialized_data1.id &&
            original_data.name == deserialized_data1.name &&
            original_data.email == deserialized_data1.email &&
            original_data.score == deserialized_data1.score &&
            original_data.active == deserialized_data1.active
        );
        
        std::cout << "\n数据一致性检查: " << (data_match ? "✓ 通过" : "✗ 失败") << "\n";
        
    } catch (const std::exception& e) {
        std::cerr << "错误: " << e.what() << "\n";
    }
}

/**
 * @brief 测试Player结构体的序列化和反序列化（包含复杂类型）
 */
void test_player_struct() {
    std::cout << "\n========== Player结构体测试 ==========\n";
    
    try {
        // 创建原始数据
        game::PlayerMsg original_data;
        original_data.id = 98765;
        original_data.username = "勇敢的战士";
        original_data.level = 42;
        original_data.experience = 123456;
        original_data.health = 100;
        original_data.mana = 75;
        
        // 设置背包物品ID列表
        std::vector<uint32_t> inventory_items = {1001, 1002, 1003, 2001, 2002};
        original_data.inventory_items = inventory_items;
        
        original_data.created_at = 1640995200;  // 2022-01-01 00:00:00 UTC
        original_data.last_login = 1640995200 + 86400;  // 一天后
        
        std::cout << "原始数据:\n";
        std::cout << "  ID: " << original_data.id << "\n";
        std::cout << "  用户名: " << original_data.username << "\n";
        std::cout << "  等级: " << original_data.level << "\n";
        std::cout << "  经验值: " << original_data.experience << "\n";
        std::cout << "  生命值: " << original_data.health << "\n";
        std::cout << "  魔法值: " << original_data.mana << "\n";
        std::cout << "  背包物品数量: " << original_data.inventory_items.size() << "\n";
        
        // 序列化
        flatbuffers::FlatBufferBuilder builder(1024);
        auto fb_offset = flatbuffers::serialize<::game::Player>(builder, original_data);
        builder.Finish(fb_offset);
        
        // 获取序列化数据
        const uint8_t* buffer_data = builder.GetBufferPointer();
        size_t buffer_size = builder.GetSize();
        std::vector<uint8_t> serialized_data(buffer_data, buffer_data + buffer_size);
        
        print_hex_data(serialized_data, "Player序列化数据");
        
        // 反序列化
        const game::Player* fb_player = flatbuffers::GetRoot<game::Player>(buffer_data);
        game::PlayerMsg deserialized_data = flatbuffers::from_flatbuffer<game::PlayerMsg>(fb_player);
        
        std::cout << "\n反序列化数据:\n";
        std::cout << "  ID: " << deserialized_data.id << "\n";
        std::cout << "  用户名: " << deserialized_data.username << "\n";
        std::cout << "  等级: " << deserialized_data.level << "\n";
        std::cout << "  经验值: " << deserialized_data.experience << "\n";
        std::cout << "  生命值: " << deserialized_data.health << "\n";
        std::cout << "  魔法值: " << deserialized_data.mana << "\n";
        std::cout << "  背包物品: ";
        for (uint32_t item_id : deserialized_data.inventory_items) {
            std::cout << item_id << " ";
        }
        std::cout << "\n";
        
        // 验证数据一致性
        bool data_match = (
            original_data.id == deserialized_data.id &&
            original_data.username == deserialized_data.username &&
            original_data.level == deserialized_data.level &&
            original_data.experience == deserialized_data.experience &&
            original_data.health == deserialized_data.health &&
            original_data.mana == deserialized_data.mana &&
            original_data.inventory_items == deserialized_data.inventory_items
        );
        
        std::cout << "\n数据一致性检查: " << (data_match ? "✓ 通过" : "✗ 失败") << "\n";
        
    } catch (const std::exception& e) {
        std::cerr << "错误: " << e.what() << "\n";
    }
}

/**
 * @brief 测试带有废弃字段的结构体
 */
void test_deprecated_fields() {
    std::cout << "\n========== 废弃字段过滤测试 ==========\n";
    
    try {
        // table_vs_struct_demo.fbs中Player表包含一个废弃字段old_score
        demo::PlayerMsg original_data;
        original_data.id = 55555;
        original_data.name = "测试玩家";
        original_data.email = "test@example.com";
        original_data.level = 10;
        original_data.health = 80;
        original_data.mana = 40;
        
        // 设置背包
        std::vector<uint32_t> inventory = {10001, 10002, 10003};
        original_data.inventory = inventory;
        
        std::cout << "原始数据 (注意: old_score字段被自动过滤):\n";
        std::cout << "  ID: " << original_data.id << "\n";
        std::cout << "  姓名: " << original_data.name << "\n";
        std::cout << "  邮箱: " << original_data.email << "\n";
        std::cout << "  等级: " << original_data.level << "\n";
        std::cout << "  生命值: " << original_data.health << "\n";
        std::cout << "  魔法值: " << original_data.mana << "\n";
        std::cout << "  背包物品数量: " << original_data.inventory.size() << "\n";
        std::cout << "  注意: old_score字段已被自动过滤，不会出现在生成的结构体中\n";
        
        // 序列化
        flatbuffers::FlatBufferBuilder builder(1024);
        auto fb_offset = flatbuffers::serialize<::demo::Player>(builder, original_data);
        builder.Finish(fb_offset);
        
        // 获取序列化数据
        const uint8_t* buffer_data = builder.GetBufferPointer();
        size_t buffer_size = builder.GetSize();
        std::vector<uint8_t> serialized_data(buffer_data, buffer_data + buffer_size);
        
        print_hex_data(serialized_data, "带废弃字段过滤的序列化数据");
        
        // 反序列化
        const demo::Player* fb_player = flatbuffers::GetRoot<demo::Player>(buffer_data);
        demo::PlayerMsg deserialized_data = flatbuffers::from_flatbuffer<demo::PlayerMsg>(fb_player);
        
        std::cout << "\n反序列化数据:\n";
        std::cout << "  ID: " << deserialized_data.id << "\n";
        std::cout << "  姓名: " << deserialized_data.name << "\n";
        std::cout << "  邮箱: " << deserialized_data.email << "\n";
        std::cout << "  等级: " << deserialized_data.level << "\n";
        std::cout << "  生命值: " << deserialized_data.health << "\n";
        std::cout << "  魔法值: " << deserialized_data.mana << "\n";
        std::cout << "  背包物品数量: " << deserialized_data.inventory.size() << "\n";
        
        std::cout << "\n✓ 废弃字段过滤功能正常工作\n";
        
    } catch (const std::exception& e) {
        std::cerr << "错误: " << e.what() << "\n";
    }
}

/**
 * @brief 性能基准测试
 */
void performance_benchmark() {
    std::cout << "\n========== 性能基准测试 ==========\n";
    
    const int iterations = 10000;
    
    // 创建测试数据
    comm::UserMsg test_data;
    test_data.id = 12345;
    test_data.name = "性能测试用户";
    test_data.email = "benchmark@example.com";
    test_data.score = 9999;
    test_data.active = true;
    
    auto start_time = std::chrono::high_resolution_clock::now();
    
    // 序列化性能测试
    std::vector<std::vector<uint8_t>> serialized_buffers;
    serialized_buffers.reserve(iterations);
    
    for (int i = 0; i < iterations; ++i) {
        flatbuffers::FlatBufferBuilder builder(256);
        auto fb_offset = flatbuffers::serialize<::comm::User>(builder, test_data);
        builder.Finish(fb_offset);
        
        const uint8_t* buffer_data = builder.GetBufferPointer();
        size_t buffer_size = builder.GetSize();
        serialized_buffers.emplace_back(buffer_data, buffer_data + buffer_size);
    }
    
    auto serialize_time = std::chrono::high_resolution_clock::now();
    
    // 反序列化性能测试
    std::vector<comm::UserMsg> deserialized_data;
    deserialized_data.reserve(iterations);
    
    for (const auto& buffer : serialized_buffers) {
        const comm::User* fb_user = flatbuffers::GetRoot<comm::User>(buffer.data());
        deserialized_data.emplace_back(flatbuffers::from_flatbuffer<comm::UserMsg, comm::User>(fb_user));
    }
    
    auto end_time = std::chrono::high_resolution_clock::now();
    
    // 计算时间
    auto serialize_duration = std::chrono::duration_cast<std::chrono::microseconds>(
        serialize_time - start_time);
    auto deserialize_duration = std::chrono::duration_cast<std::chrono::microseconds>(
        end_time - serialize_time);
    auto total_duration = std::chrono::duration_cast<std::chrono::microseconds>(
        end_time - start_time);
    
    std::cout << "迭代次数: " << iterations << "\n";
    std::cout << "序列化时间: " << serialize_duration.count() << " 微秒\n";
    std::cout << "反序列化时间: " << deserialize_duration.count() << " 微秒\n";
    std::cout << "总时间: " << total_duration.count() << " 微秒\n";
    std::cout << "平均序列化时间: " << serialize_duration.count() / iterations << " 微秒/次\n";
    std::cout << "平均反序列化时间: " << deserialize_duration.count() / iterations << " 微秒/次\n";
    std::cout << "序列化吞吐量: " << (iterations * 1000000.0 / serialize_duration.count()) << " 次/秒\n";
    std::cout << "反序列化吞吐量: " << (iterations * 1000000.0 / deserialize_duration.count()) << " 次/秒\n";
}

} // namespace demo

int main() {
    std::cout << "FlatBuffer结构体生成器演示程序\n";
    std::cout << "=====================================\n";
    
    try {
        // 测试User结构体
        demo::test_user_struct();
        
        // 测试Player结构体（包含复杂类型）
        demo::test_player_struct();
        
        // 测试废弃字段过滤
        demo::test_deprecated_fields();
        
        // 性能基准测试
        demo::performance_benchmark();
        
        std::cout << "\n========== 所有测试完成 ==========\n";
        std::cout << "✓ 结构体生成功能正常\n";
        std::cout << "✓ 序列化/反序列化功能正常\n";
        std::cout << "✓ 废弃字段过滤功能正常\n";
        std::cout << "✓ 性能表现良好\n";
        
    } catch (const std::exception& e) {
        std::cerr << "程序执行失败: " << e.what() << "\n";
        return 1;
    }
    
    return 0;
}
